package com.yunyouyi.CacheModel;

import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.ReentrantLock;

public class SimpleCache<K,V> {
    protected final Map<K, CacheEntry<V>> cache;
    protected final ReentrantLock lock =  new ReentrantLock();
    private final ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);

    // 默认过期时间（秒），可选
    private static final long DEFAULT_EXPIRE_SECONDS = 60;

    // 默认构造器：使用 HashMap
    public SimpleCache() {
        this(new HashMap<>());
        scheduler.scheduleAtFixedRate(this::cleanExpired, 10, 30, TimeUnit.SECONDS);
    }
    // 新增构造器：允许传入自定义 Map（支持 LRU）
    public SimpleCache(Map<K, CacheEntry<V>> map) {
        this.cache = map;
        scheduler.scheduleAtFixedRate(this::cleanExpired, 10, 30, TimeUnit.SECONDS);
    }

    /**
     * 存入缓存，默认60s
     */
    public void put(K key, V value) {
        put(key, value, DEFAULT_EXPIRE_SECONDS);
    }

    /**
     * 存入缓存，指定过期时间（秒）
     */
    public void put(K key, V value, long expireSeconds) {
        lock.lock();
        try {
            long expireTime = expireSeconds > 0 ? System.currentTimeMillis() + expireSeconds * 1000 : Long.MAX_VALUE;
            onPut(key, new CacheEntry<>(value, expireTime)); // 使用钩子方法
        } finally {
            lock.unlock();
        }
    }

    protected void onPut(K key, CacheEntry<V> entry) {
        cache.put(key, entry);
    }

    /**
     * 获取缓存值，若已过期则返回 null
     */
    public V get(K key) {
        lock.lock();
        try {
            CacheEntry<V> entry = cache.get(key);
            if (entry == null) {
                return null;
            }
            if (entry.isExpired()) {
                cache.remove(key); // 清理过期项
                return null;
            }
            return entry.value;
        } finally {
            lock.unlock();
        }
    }

    /**
     * 立即删除某个 key
     */
    public void remove(K key) {
        lock.lock();
        try {
            cache.remove(key);
        } finally {
            lock.unlock();
        }
    }

    /**
     * 清理所有过期的缓存项（供定时任务调用）
     */
    protected void cleanExpired() {
        lock.lock();
        try {
            cache.entrySet().removeIf(entry -> entry.getValue().isExpired());
        } finally {
            lock.unlock();
        }
    }

    /**
     * 关闭缓存，停止定时任务（优雅关闭）
     */
    public void shutdown() {
        scheduler.shutdown();
        try {
            if (!scheduler.awaitTermination(5, TimeUnit.SECONDS)) {
                scheduler.shutdownNow();
            }
        } catch (InterruptedException e) {
            scheduler.shutdownNow();
            Thread.currentThread().interrupt();
        }
    }

    /**
     * 获取当前缓存大小（调试用）
     */
    public int size() {
        lock.lock();
        try {
            return cache.size();
        } finally {
            lock.unlock();
        }
    }
}